package org.dfl.plugin.views.actions;

import java.util.Set;

import org.dfl.core.data.Token;
import org.dfl.core.data.types.TypeManager;
import org.dfl.core.model.Place;
import org.dfl.plugin.DflPlugin;
import org.dfl.plugin.dialogs.DialogsManager;
import org.dfl.plugin.views.debug.HistoriesTreeView;
import org.dfl.plugin.views.debug.TokensTreeView;
import org.dfl.plugin.views.debug.model.HistoryTreeElem;
import org.dfl.plugin.views.debug.model.TokenTreeElem;
import org.dfl.plugin.views.debug.model.TokensTreeViewRoot;
import org.dfl.plugin.views.debug.model.TreeElem;
import org.eclipse.jface.action.IAction;
import org.eclipse.ui.IViewActionDelegate;
import org.eclipse.ui.IViewPart;
import org.eclipse.ui.actions.ActionDelegate;

/**
 * action that provide pasting tokens. It's used in a TokensTreeView (see
 * mapping in plugin.xml file)
 * 
 * @author Piotr Wlodarczyk
 * 
 */
public class PasteTokenAction extends ActionDelegate implements
		IViewActionDelegate {
	/*
	 * (non-Javadoc)
	 * 
	 * @see org.eclipse.ui.actions.ActionDelegate#run(org.eclipse.jface.action.IAction)
	 */
	public void run(IAction action) {
		if (view != null && view.getCommonViewer().getInput() != null
				&& !view.getHistoryTreeElems().isEmpty()) {
			TokensTreeViewRoot root = (TokensTreeViewRoot) view
					.getCommonViewer().getInput();
			Place place = root.getHistoryTreeElems().iterator().next()
					.getPlace();

			HistoriesTreeView historiesTreeView = HistoriesTreeView.getView();
			TokensTreeView tokensTreeView = TokensTreeView.getView();
			// place listeners have to be removed before
			if (historiesTreeView != null)
				historiesTreeView.stopListenPlace();
			if (tokensTreeView != null)
				tokensTreeView.stopListenPlace();

			Set<TreeElem> toPasteElems = CopyContentAction.getCopyElems();
			if (toPasteElems.isEmpty()) {
				return;
			}
			for (TreeElem toPasteElem : toPasteElems) {
				if (!(toPasteElem instanceof TokenTreeElem)) {
					return;
				}
			}
			
			if (root.getHistoryTreeElems().size() > 1
					&& !DialogsManager
							.openOkCancelDialog(
									"Confirm",
									"You have selected multiple histories.\n All tokens will be pasted to each of those histories.\n Are you sure to continue?")) {
				return;
			}

			for (HistoryTreeElem historyTreeElem : root.getHistoryTreeElems()) {
				for (TreeElem toPasteElem : toPasteElems) {
					if (!(toPasteElem instanceof TokenTreeElem)) {
						continue;
					} else {
						Object data = ((TokenTreeElem) toPasteElem).getValue();
						if (!TypeManager.isValidDataElem(data, place
								.getTypeContainer().getType())) {
							DialogsManager
									.openErrorDialog("Pasted token has a wrong type");
							return;
						}
						Token token = new Token(data, historyTreeElem
								.getHistory());
						synchronized (DflPlugin.class) {
							historyTreeElem.getTokens().add(token);
							place.addToken(token);
							root
									.addChild(new TokenTreeElem(root, token,
											place));
						}
					}
				}
			}
			// restore place listeners
			if (historiesTreeView != null)
				historiesTreeView.startListenPlace();
			if (tokensTreeView != null)
				tokensTreeView.startListenPlace();

			view.getCommonViewer().refresh();
		}
	}

	TokensTreeView view;

	public void init(IViewPart view) {
		if (view instanceof TokensTreeView)
			this.view = (TokensTreeView) view;
	}
}
